using System;
using System.Collections;
using System.Collections.Generic;
using Server.Items;
using Server.Mobiles;


namespace Server.Items
{
	public class SaveStone : Item
	{
		public static int StoneX = 1415;
		public static int StoneY = 1689;
		public static Map StoneMap = Map.Felucca;

		public static List<TradeMobile> TradePets;

		public static Hashtable LastBids;
		public static Hashtable PlayerBids;

		public static void Initialize()
		{
			// to leave one and only one instance of savestone to save static array lists
			List<SaveStone> list = CommonTools.FindItemsOfType<SaveStone>();

			if ( !( list.Count > 0 ) )
			{
				SaveStone ss = new SaveStone();

				// Britain Bank of Felucca, next to Nerun's Championspawn Controller
				ss.MoveToWorld( new Point3D( StoneX, StoneY, StoneMap.GetAverageZ( StoneX, StoneY ) ), StoneMap );
			}
		}


		[Constructable]
		public SaveStone() : base( 0x116B )
		{
			Name = "a Vendor Mall Saving Stone";
			Movable = false;
			Visible = false;

			TradePets = new List<TradeMobile>();

			LastBids = new Hashtable();
			PlayerBids = new Hashtable();
		}

		public SaveStone( Serial serial ) : base( serial )
		{ 
		} 


		public override void OnDelete()
		{

			base.OnDelete();
		}

		public static List<StaffBid> ReloadVendorBids()
		{
			List<StaffBid> list = new List<StaffBid>();

			foreach ( BidByItem bbi in LastBids.Values )
			{
				Item item = bbi.m_itemobj as Item;

				if ( item != null && item.RootParent is IHardsellable && !( item.RootParent is CommissionedVendor ) 
					&& bbi.m_byprice != null && bbi.m_byprice.Count > 0 )
				{
					IHardsellable hs = item.RootParent as IHardsellable;
					Mobile vendor = item.RootParent as Mobile;

					if ( hs.Manager != null && !hs.Manager.Deleted && vendor != null && !vendor.Deleted )
					{
						TradeItem ti = VendorManager.GetTradeItem( hs, item );
						StaffBid sb = new StaffBid( ti.Description, hs.Manager, vendor, bbi.m_start, bbi.Expire, (int)bbi.m_byprice[0].m_bid );

						list.Add( sb );
					}
				}
			}

			return list;
		}

		public override void Serialize( GenericWriter writer )
		{
			base.Serialize( writer );
			writer.Write( (int) 0 ); // version

			if ( TradePets != null && TradePets.Count > 0 )
			{
				writer.Write( (int) TradePets.Count );

				for ( int i = 0; i < TradePets.Count; i++ )
				{
					TradeMobile tm = TradePets[i];

					writer.Write( (Mobile) tm.m_owner );
					writer.Write( (Mobile) tm.m_vendor );
					writer.Write( (Mobile) tm.m_pet );
				}
			}
			else
				writer.Write( (int) 0 );

			if ( LastBids != null && LastBids.Count > 0 )
			{
				writer.Write( (int) LastBids.Count );

				foreach ( DictionaryEntry de in LastBids )
				{
					writer.Write( (Mobile) de.Key );

					BidByItem bbi = (BidByItem)de.Value;

					writer.Write( (Item) bbi.m_itemobj );
					writer.Write( (TimeSpan) bbi.m_duration );
					writer.Write( (DateTime) bbi.m_start );

					writer.Write( (int) bbi.m_byprice.Count );
					foreach ( BidItem bi in bbi.m_byprice )
					{
						writer.Write( (Mobile) bi.m_bider );
						writer.Write( (int) bi.m_bid );
					}
				}
			}
			else
				writer.Write( (int) 0 );

			if ( PlayerBids != null && PlayerBids.Count > 0 )
			{
				writer.Write( (int) PlayerBids.Count );

				foreach ( DictionaryEntry de in PlayerBids )
				{
					writer.Write( (Mobile) de.Key );

					List<BidRecord> list = (List<BidRecord>)de.Value;

					writer.Write( (int) list.Count );
					foreach ( BidRecord br in list )
					{
						writer.Write( (Serial) br.m_serial );
						writer.Write( (string) br.m_name );
						writer.Write( (Mobile) br.m_vendor );
						writer.Write( (int) br.m_bid );
						writer.Write( (DateTime) br.m_expire );
						writer.Write( (string) br.m_comment );
					}
				}
			}
			else
				writer.Write( (int) 0 );
		}

		public override void Deserialize( GenericReader reader )
		{
			base.Deserialize( reader );
			int version = reader.ReadInt();

			TradePets = new List<TradeMobile>();
			LastBids = new Hashtable();
			PlayerBids = new Hashtable();

			// Reload TradePets
			for ( int i = reader.ReadInt(); i > 0; i-- )
			{
				TradeMobile tm 
					= new TradeMobile( reader.ReadMobile(), reader.ReadMobile(), (BaseCreature)reader.ReadMobile() );

				TradePets.Add( tm );
			}

			// Reload LastBid
			for ( int i = reader.ReadInt(); i > 0; i-- )
			{
				Mobile owner = reader.ReadMobile();

				BidByItem bbi = new BidByItem( (object)reader.ReadItem(), reader.ReadTimeSpan() );
				bbi.m_start = reader.ReadDateTime();

				for ( int j = reader.ReadInt(); j > 0; j-- )
				{
					bbi.m_byprice.Add( new BidItem( reader.ReadMobile(), reader.ReadInt() ) );
					bbi.m_byprice.Sort( new BidItemComparer() );
				}

				LastBids[owner] = bbi;
			}

			// Reload PlayerBids
			for ( int i = reader.ReadInt(); i > 0; i-- )
			{
				Mobile owner = reader.ReadMobile();
				List<BidRecord> list = new List<BidRecord>();

				for ( int j = reader.ReadInt(); j > 0; j-- )
				{
					BidRecord br =
						new BidRecord( (Serial)reader.ReadInt(), reader.ReadString(), reader.ReadMobile(), 
						reader.ReadInt(), reader.ReadDateTime(), reader.ReadString() );

					list.Add( br );
				}

				PlayerBids[owner] = list;
			}
		}

	}

	public class StaffBid
	{
		public string m_itname;
		public Mobile m_manager;
		public Mobile m_vendor;
		public DateTime m_start;
		public DateTime m_expire;
		public int m_bid;

		public StaffBid( string itname, Mobile manager, Mobile vendor, DateTime start, DateTime expire, int bid )
		{
			m_itname = itname;
			m_manager = manager;
			m_vendor = vendor;
			m_start = start;
			m_expire = expire;
			m_bid = bid;
		}
	}
}